package com.lightsh.gui;

import com.lightsh.configure.Configure;
import com.lightsh.utility.Utility;

import android.content.Context;
import android.graphics.Canvas;
import android.graphics.Color;
import android.graphics.Paint;
import android.util.AttributeSet;
import android.util.Log;
import android.view.KeyEvent;
import android.view.MotionEvent;
import android.view.SurfaceHolder;
import android.view.SurfaceView;
import android.view.SurfaceHolder.Callback;

/**
 * 游戏的主界面视图
 * @author Lightsh
 *
 */
public class GameSurfaceView extends SurfaceView implements Callback, Runnable{

	private static final boolean DEBUG = true;
	private static final boolean DRAW_TRACK = true;
	private static final String TAG = "GameSurfaceView";
	private static int REFRESH_INTERVAL = (int) (1000 / Configure.PHYSICS_TIME_STEP);
	private static long REFRESH_START_TIME;
	private static long REFRESH_USED_TIME;
	private boolean mbRunning = false;
	private SurfaceHolder mSurfaceHolder; 
    private Thread mDrawThread;
    
    private BaseScreen mGameScreen;
    
    /**
     * 请在初始化该类后,调用{@link #setGameScreen(BaseScreen)}来设置gameScreen,否则会抛运行时异常
     * @param context
     */
	public GameSurfaceView(Context context) {
		super(context);
		init();
	}
	public GameSurfaceView(Context context, AttributeSet as){
		super(context, as);
		init();
	}
	private void init(){
		mSurfaceHolder = getHolder();
		mSurfaceHolder.addCallback(this);
        this.setKeepScreenOn(true);
	}
	
	@Override
	public void surfaceChanged(SurfaceHolder holder, int format, int width,
			int height) {
		logTip("surfaceChanged");
	}
	private void logTip(String msg){
		if(DEBUG){
			Log.d(TAG, msg == null ? "" : msg);
		}
	}

	@Override
	public void surfaceCreated(SurfaceHolder holder) {
		logTip("surfaceCreated");
		startDrawThread();
	}

	@Override
	public void surfaceDestroyed(SurfaceHolder holder) {
		logTip("surfaceDestroyed");
		mbRunning = false;
		mGameScreen.onScreenPause();
	}
	
	private void startDrawThread(){
		
		if(mGameScreen == null){
			throw new RuntimeException("you forget to setGameScreen() before start draw!");
		}		
		mDrawThread = new Thread(this);
		mDrawThread.start();
		mbRunning = true;
	}
	
	@Override
	public void run() {		
		while(mbRunning){
			REFRESH_START_TIME = System.currentTimeMillis();
			update();
			draw();
			REFRESH_USED_TIME = System.currentTimeMillis() - REFRESH_START_TIME;
			if(REFRESH_USED_TIME < REFRESH_INTERVAL){
				//logTip("draw used time: " + REFRESH_USED_TIME);
				try{
					Thread.sleep(REFRESH_INTERVAL - REFRESH_USED_TIME);
				}catch(Exception ignore){
				}
			}
		}
		
	}
	
	/**
	 * 该方法完成所有的数据更新操作
	 */
	private void update(){
		mGameScreen.update();
	}
	/**
	 * 该方法完成所有画面的绘制工作
	 */
	private void draw(){
		Canvas canvas = mSurfaceHolder.lockCanvas();
		try{            
            mGameScreen.draw(canvas);
		}catch(Exception e){
			e.printStackTrace();
		}finally{
			if(canvas != null){
				mSurfaceHolder.unlockCanvasAndPost(canvas);
			}
		}
	}
	
	/**
	 * 设置实际负责游戏画面绘制和响应的screen
	 * <br/>请注意，必须在游戏开始绘制时调用该方法,否则会抛运行时异常
	 * @param gameScreen
	 */
	public void setGameScreen(BaseScreen gameScreen){
		if(gameScreen == null){
			throw new IllegalArgumentException("gameScreen cant be null");
		}
		mGameScreen = gameScreen;
		// FIXME 是否可以考虑在这里设置REFRESH_INTERVAL的值
		Utility.fixme();
//		REFRESH_INTERVAL = (int) (1000 * mGameScreen.getTimeStep());
	}
	@Override
	public boolean onTouchEvent(MotionEvent event) {
		return mGameScreen.onTouchEvent(event);
	}
	
	
}
